#!/usr/bin/env python
# -*- coding: utf-8 -*-
# @Time    : 2025/11/1 17:41
# @Author  : summer
# @Email   : 610658552@qq.com
# @File    : ser_dingtalk_config.py
# @Software: PyCharm
# @Desc    :
from rest_framework import serializers

from sdingding.models import DingTalkConfig  # 替换为实际模型所在路径


class DingTalkConfigSerializer(serializers.ModelSerializer):
    """
    DingTalkConfig序列化器：
    - 核心校验：access_token和secret组合唯一（全局不重复）
    - 不返回is_delete和pt_flag字段
    - 基础校验：名称非空唯一、Token非空
    """
    # 时间字段格式化（只读）
    create_time = serializers.DateTimeField(format="%Y-%m-%d %H:%M:%S", read_only=True)
    update_time = serializers.DateTimeField(format="%Y-%m-%d %H:%M:%S", read_only=True)

    class Meta:
        model = DingTalkConfig
        # 仅包含需要返回的字段，移除is_delete和pt_flag
        fields = [
            "id", "name", "access_token", "secret", "description",
            "create_time", "update_time", "sort_num", "is_active"
        ]
        read_only_fields = ["id", "create_time", "update_time"]

    def validate_name(self, value):
        """校验配置名称：非空且全局唯一"""
        value = value.strip()
        if not value:
            raise serializers.ValidationError("配置名称不能为空")

        queryset = DingTalkConfig.objects.all()
        if self.instance is None:  # 新增场景
            if queryset.filter(name=value).exists():
                raise serializers.ValidationError(f"配置名称「{value}」已存在")
        else:  # 更新场景：排除当前实例
            if queryset.exclude(id=self.instance.id).filter(name=value).exists():
                raise serializers.ValidationError(f"配置名称「{value}」已存在")
        return value

    def validate_access_token(self, value):
        """校验Token：非空"""
        value = value.strip()
        if not value:
            raise serializers.ValidationError("钉钉机器人Token不能为空")
        return value

    def validate(self, data):
        """核心组合校验：access_token和secret不能同时与其他记录重复"""
        # 1. 提取当前数据（处理空值和去空格）
        current_token = data.get("access_token", "").strip()
        current_secret = data.get("secret", "").strip() or ""  # 空值统一处理为""

        # 2. 全局校验（所有记录均参与）
        queryset = DingTalkConfig.objects.all()

        # 3. 更新场景：排除当前实例
        if self.instance is not None:
            queryset = queryset.exclude(id=self.instance.id)

        # 4. 组合唯一性校验
        if queryset.filter(access_token=current_token, secret=current_secret).exists():
            # 脱敏显示敏感信息
            secret_display = current_secret[:6] + "****" if current_secret else "空"
            raise serializers.ValidationError(
                f"已存在相同的机器人Token和加签密钥组合（Token：{current_token[:10]}****，Secret：{secret_display}）"
            )

        # 5. 新增场景必传字段校验
        if self.instance is None:
            required_fields = ["name", "access_token"]
            missing = [f for f in required_fields if f not in data]
            if missing:
                raise serializers.ValidationError(f"缺少必填字段：{', '.join(missing)}")

        return data
